﻿using System;
using System.Collections.Generic;
using Assist;
using Autodesk.Revit.ApplicationServices;
using Autodesk.Revit.Attributes;
using Autodesk.Revit.DB;
using Autodesk.Revit.UI;
using YArchitech.Controls;
using YArchitech.Revit;
using YArchitech.Revit.RevitExtension;
using YJKRevitView;

namespace YJKRevitAxisModule
{
	[Regeneration(RegenerationOption.Manual)]
	[Transaction(TransactionMode.Manual)]
	internal class CmdGridsAlignment : YJKCommandManual
	{
		protected override Result YJKExcute(ExternalCommandData cmdData, ref string message, ElementSet elements)
		{
			int num = Convert.ToInt32(cmdData.Application.Application.VersionNumber);
			if (2015 >= num)
			{
				YJKMessageBox.Show("此功能只在Revit2016及其以上版本可用");
				return Autodesk.Revit.UI.Result.Succeeded;
			}
			CmdViewType types = (CmdViewType)11;
			if (SwitchView.SetUsableView(types, cmdData) != Autodesk.Revit.UI.Result.Succeeded)
			{
				return Autodesk.Revit.UI.Result.Failed;
			}
			Transaction transaction = new Transaction(this.m_doc, this.ToString());
			transaction.Start();
			Result result = this.GridsAlign(cmdData, ref message);
            if (result == Autodesk.Revit.UI.Result.Succeeded)
			{
				transaction.Commit();
				return result;
			}
			transaction.RollBack();
			return result;
		}

		private Result GridsAlign(ExternalCommandData cmdData, ref string message)
		{
			Document document = cmdData.Application.ActiveUIDocument.Document;
			Application application = cmdData.Application.Application;
			try
			{
				IList<Reference> list = cmdData.Application.ActiveUIDocument.Selection.PickObjects((Autodesk.Revit.UI.Selection.ObjectType)1, new SingleGridFilter(), "框选要对齐的平行轴线");
				if (list.Count == 0)
				{
					YJKMessageBox.Show("没有选中任何轴线。");
					return Autodesk.Revit.UI.Result.Cancelled;
				}
				XYZ xyz = cmdData.Application.ActiveUIDocument.Selection.PickPoint("请点取新的对齐位置点：");
				foreach (Reference reference in list)
				{
					Grid grid = RevitVersionFuncs.GetElement(this.m_doc, reference.ElementId) as Grid;
					bool bIsStartBubbleVisible = grid.IsBubbleVisibleInView((DatumEnds)0, this.m_doc.ActiveView);
					bool bIsEndBubbleVisible = grid.IsBubbleVisibleInView((DatumEnds)1, this.m_doc.ActiveView);
					grid.get_Parameter(BuiltInParameter.DATUM_TEXT).AsString();


                    Parameter parameter = grid.get_Parameter(BuiltInParameter.DATUM_TEXT);
                    string text = parameter.AsString();

					XYZ hyendPoint = grid.Curve.GetEndPoint(0);
					XYZ hyendPoint2 = grid.Curve.GetEndPoint(1);
					if (grid.Curve is Line)
					{
						Line line = YJKLineEx.YJKGetUnBound(hyendPoint, hyendPoint2 - hyendPoint);
						double num = hyendPoint.DistanceTo(xyz);
						double num2 = hyendPoint2.DistanceTo(xyz);
						XYZ xyz2;
						XYZ xyz3;
						if (num >= num2)
						{
							xyz2 = line.Project(xyz).XYZPoint;
							xyz3 = hyendPoint;
						}
						else
						{
							xyz3 = line.Project(xyz).XYZPoint;
							xyz2 = hyendPoint2;
						}

                        Grid grid2 = document.YjkNewGrid(YJKLineEx.YJKGetBound(xyz3, xyz2));
                        grid2.ExtendToAllLevels();
                        grid2.ChangeTypeId(grid.GetGridType().Id);
                        document.Delete(grid.Id);
                        Parameter parameter2 = grid2.get_Parameter(BuiltInParameter.DATUM_TEXT);
                        parameter2.Set(text);
                        this.IsShowBubble(bIsStartBubbleVisible, bIsEndBubbleVisible, grid2);








                        //double z = grid.GetCurvesInView(1, document.ActiveView)[0].GetEndPoint(0).Z;
                        //Curve curve = YJKLineEx.YJKGetBound(new XYZ(xyz2.X, xyz2.Y, z), new XYZ(xyz3.X, xyz3.Y, z));
                        //grid.SetCurveInView(1, document.ActiveView, curve);
                        //this.IsShowBubble(bIsStartBubbleVisible, bIsEndBubbleVisible, grid);
					}
					else if (grid.Curve is Arc)
					{
                        Arc arc = grid.Curve as Arc;
                        Line line2 = YJKLineEx.YJKGetBound(arc.Center, xyz);
                        line2.MakeUnbound();
                        Arc arc2 = cmdData.Application.ActiveUIDocument.Document.CreatYJKArc(arc.Center, arc.Radius, 0.0, Math.PI * 2, XYZ.BasisX, XYZ.BasisY);
                        IntersectionResultArray intersectionResultArray = new IntersectionResultArray();
                        line2.Intersect(arc2, out intersectionResultArray);
                        XYZ xyzpoint = intersectionResultArray.get_Item(0).XYZPoint;
                        XYZ arcMidPoint = ArcAssistFunc.GetArcMidPoint(arc);
                        double num3 = hyendPoint.DistanceTo(xyzpoint);
                        double num4 = hyendPoint2.DistanceTo(xyzpoint);
                        XYZ xyz2;
                        XYZ xyz3;
                        XYZ radianPnt;
                        if (num3 >= num4)
                        {
                            xyz3 = xyzpoint;
                            xyz2 = hyendPoint;
                            radianPnt = arcMidPoint;
                        }
                        else
                        {
                            xyz3 = hyendPoint2;
                            xyz2 = xyzpoint;
                            radianPnt = arcMidPoint;
                        }

                        Grid grid3 = document.YjkNewGrid(application.CreatYJKArc(xyz3, xyz2, radianPnt));
                        grid3.ExtendToAllLevels();
                        grid3.ChangeTypeId(grid.GetGridType().Id);
                        document.Delete(grid.Id);
                        Parameter parameter3 = grid3.get_Parameter(BuiltInParameter.DATUM_TEXT);
                        parameter3.Set(text);
                        this.IsShowBubble(bIsStartBubbleVisible, bIsEndBubbleVisible, grid3);

                        //double z2 = grid.GetCurvesInView(1, document.ActiveView)[0].GetEndPoint(0).Z;
                        //Curve curve2 = application.CreatYJKArc(new XYZ(xyz2.X, xyz2.Y, z2), new XYZ(xyz3.X, xyz3.Y, z2), new XYZ(xyz4.X, xyz4.Y, z2));
                        //grid.SetCurveInView(1, document.ActiveView, curve2);
                        //this.IsShowBubble(bIsStartBubbleVisible, bIsEndBubbleVisible, grid);
					}
				}
				this.m_doc.Regenerate();
				cmdData.Application.ActiveUIDocument.RefreshActiveView();
			}
			catch (Exception)
			{
				return Autodesk.Revit.UI.Result.Failed;
			}
			return Autodesk.Revit.UI.Result.Succeeded;
		}

		private void IsShowBubble(bool bIsStartBubbleVisible, bool bIsEndBubbleVisible, Grid newGrid)
		{
			if (bIsStartBubbleVisible)
			{
				newGrid.ShowBubbleInView((DatumEnds)0, this.m_doc.ActiveView);
			}
			else
			{
				newGrid.HideBubbleInView((DatumEnds)0, this.m_doc.ActiveView);
			}
			if (bIsEndBubbleVisible)
			{
				newGrid.ShowBubbleInView((DatumEnds)1, this.m_doc.ActiveView);
				return;
			}
			newGrid.HideBubbleInView((DatumEnds)1, this.m_doc.ActiveView);
		}
	}
}
